package com.fafa.pos.util.newland;

import android.util.Log;

import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
import java.io.UnsupportedEncodingException;
import java.security.Key;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

public class CryptoUtil {
//	private static DeviceLogger log = DeviceLoggerFactory.getLogger(CryptoUtil.class);
	private static final String TAG = "CryptoUtil";
	/**
	 * 十六进制组
	 */
	private static final char[] hexChar = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };



	/**
	 * SHA摘要算法，输入内容将被UTF-8编码
	 * 
	 * @param content
	 *            输入明文
	 * @return 内容摘要，40位16进制字符串
	 */
	public static String encryptBySHA(String content) {
		if (content == null) {
			return null;
		}

		try {
			MessageDigest md = MessageDigest.getInstance("SHA");
			byte[] output = md.digest(content.getBytes("UTF-8"));
			return bytesToHexStr(output);
		} catch (NoSuchAlgorithmException e) {
			Log.e(TAG,"无法加载SHA算法。"+e.getMessage());
		} catch (UnsupportedEncodingException e) {
			Log.e(TAG,"无法将输入字符串转换到utf-8编码。"+e.getMessage());
		}
		return null;
	}

    /**
     * 加密
     * @param cryptAlgorithm  算法
     * @see CrypAlgorithm
     * @param content 明文字节
     * @param key  密钥
     * @return  密文字节
     */
    public static byte[] encrypt(CrypAlgorithm cryptAlgorithm, byte[] content, byte[] key){
        if ((key == null) || (content == null)) {
            return null;
        }
        String algorithmName = cryptAlgorithm.getAlgorithmName();
        int keyLength = cryptAlgorithm.getKeyLength();
        if(key.length != keyLength){
        	Log.e(TAG,algorithmName+"算法需要"+keyLength+"字节密钥");
            return null;
        }
        try {
            Key k = new SecretKeySpec(key, cryptAlgorithm.getKeyType());
            Cipher cipher = Cipher.getInstance(algorithmName);
            cipher.init(Cipher.ENCRYPT_MODE, k);
            byte[] output = cipher.doFinal(content);
            return output;

        } catch (NoSuchAlgorithmException e){
        	Log.e(TAG,"不支持算法"+algorithmName);
        } catch (Exception e){
        	Log.e(TAG,"加密失败!");
        }
        return null;
    }


    /**
     * 解密
     * @param cryptAlgorithm 算法
     * @see CrypAlgorithm
     * @param cipherContent 十六进制表示的密文字符串
     * @param key 运算密钥
     * @return 明文字节
     */
    public static byte[] decrypt(CrypAlgorithm cryptAlgorithm, byte[] cipherContent, byte[] key){
        if ((key == null) || (cipherContent == null)) {
            return null;
        }

        String algorithmName = cryptAlgorithm.getAlgorithmName();
        int keyLength = cryptAlgorithm.getKeyLength();
        if(key.length != keyLength){
        	Log.e(TAG,algorithmName+"算法需要"+keyLength+"字节密钥");
            return null;
        }
        try {
            Key k = new SecretKeySpec(key, cryptAlgorithm.getKeyType());
            Cipher cipher = Cipher.getInstance(algorithmName);
            cipher.init(Cipher.DECRYPT_MODE, k);
            byte[] output = cipher.doFinal(cipherContent);
            return output;
        } catch (NoSuchAlgorithmException e){
        	Log.e(TAG,"不支持算法"+algorithmName);
        } catch (Exception e){
        	Log.e(TAG,"解密失败!");
        }
        return null;
    }

	/**
	 * 将byte数组转换为16进制格式的字符串
	 * 
	 * @param bytes
	 *            待转换数组
	 * @return 16进制格式的字符串
	 */
	public static String bytesToHexStr(byte[] bytes) {
		StringBuffer sb = new StringBuffer(bytes.length * 2);
		for (int i = 0; i < bytes.length; i++) {
			sb.append(hexChar[(bytes[i] & 0xf0) >>> 4]);
			sb.append(hexChar[bytes[i] & 0x0f]);
		}
		return sb.toString();
	}

	/**
	 * 将一个16进制格式的字符串转换为一个byte数组，它的长度必需为偶数，A-F部分大小不敏感。
	 * 
	 * @param s
	 *            待转换的字符串，必需符合16进制格式，不含正负号。
	 * @return 字节数组
	 */
	public static byte[] hexStrToBytes(String s) {
		int stringLength = s.length();
		if ((stringLength & 0x1) != 0) {
			throw new IllegalArgumentException("待转换的字符串长度必需为偶数。");
		}
		byte[] b = new byte[stringLength / 2];

		for (int i = 0, j = 0; i < stringLength; i += 2, j++) {
			int high = charToHex(s.charAt(i));
			int low = charToHex(s.charAt(i + 1));
			b[j] = (byte) ((high << 4) | low);
		}
		return b;
	}

	/**
	 * 将单个字符转换为16进制数字
	 * 
	 * @param c
	 *            等待转换的字符，必需为0-9 a-f A-F，不能有数字符号
	 * @return 16进制数字
	 */
	public static int charToHex(char c) {
		if ('0' <= c && c <= '9') {
			return c - '0';
		} else if ('a' <= c && c <= 'f') {
			return c - 'a' + 0xa;
		} else if ('A' <= c && c <= 'F') {
			return c - 'A' + 0xa;
		} else {
			throw new IllegalArgumentException("不符合格式的16进制字符: " + c);
		}
	}


	public static boolean isNotEmpty(String param) {
		if (null == param || param.trim().equals("")) {
			return false;
		}
		return true;
	}
}
